#include <stdio.h>
#include <assert.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdlib.h>
#include <unistd.h>

#define NUM 1024

// 文件结构体
struct FILE_ 
{
    int fd; // 文件描述符
    char buff[NUM]; // 缓冲区
    int end; // 缓冲区的下一个位置
};

typedef struct FILE_ FILE_;

// 打开文件
FILE_* fopen_(const char *pathname,const char *mode )
{
    assert(pathname);
    assert(mode);
    
    FILE_ *fp=NULL;

    if(strcmp(mode,"w")==0)
    {
        int fd=open(pathname,O_WRONLY | O_TRUNC | O_CREAT,0666);
        if(fd>=0)
        {
           fp=(FILE_*)malloc(sizeof(FILE_));
           memset(fp,0,sizeof(FILE_));

           fp->fd=fd;

        }

    }
    else if(strcmp(mode,"w+")==0)
    {

    }
    else if(strcmp(mode,"r")==0)
    {

    }
    else if(strcmp(mode,"r+")==0)
    {

    }
    else if(strcmp(mode,"a")==0)
    {
        int fd=open(pathname,O_APPEND | O_CREAT,0666);
        if(fd>=0)
        {
           fp=(FILE_*)malloc(sizeof(FILE_));
           memset(fp,0,sizeof(FILE_));

           fp->fd=fd;
        }
    }
    else if(strcmp(mode,"a+")==0)
    {

    }
    else 
    {

    }

    return fp;

}

// 写入
void fputs_(const char *str,FILE_ *fp)
{
    assert(str);
    assert(fp);

    // abcdef\0
    strcpy(fp->buff+fp->end,str);
    fp->end+=strlen(str);
    
    // for debug
    fprintf(stdout,"%s\n",fp->buff);

    // 定制刷新策略
}

// 刷新缓冲区
void fflush_(FILE_ *fp)
{
    assert(fp);

    if(fp->end>0)
    {
        write(fp->fd,fp->buff,fp->end);
        syncfs(fp->fd);
    }

}

// 关闭文件
void fclose_(FILE_ *fp)
{
   assert(fp);

   fflush_(fp);

   close(fp->fd);

   free(fp);

}

int main()
{

    FILE_ *fp=fopen_("./log.txt","w");

    if(fp==NULL)
    {
        perror("fopen_");
        exit(1);
    }

    fputs_("aaaaaa",fp);
    fputs_("bbbbbb",fp);
    fputs_("cccccc",fp);

    // fork之后父子进程代码共享，数据写时拷贝
    fork();

    fclose_(fp);

    return 0;
}
